import random

# 定义问题的参数和数据
num_regions = 5  # 区域数量
max_capacity = 20  # 自行车库存上限
demand = [15, 10, 5, 8, 12]  # 每个区域的需求量
target_region = 3  # 目标区域的索引，您可以根据需要更改

# 初始化蚁群算法参数
num_ants = 10  # 蚂蚁数量
num_iterations = 100  # 迭代次数
pheromone = [[1.0] * num_regions for _ in range(num_regions)]  # 信息素浓度矩阵
alpha = 1.0  # 信息素重要性参数
beta = 1.0  # 启发式规则重要性参数
evaporation_rate = 0.5  # 信息素蒸发率

# 定义蚂蚁类
class Ant:
    def __init__(self):
        self.current_region = random.randint(0, num_regions - 1)
        self.tour = []

    def select_next_region(self, target_region):
        # 在选择下一个区域时，考虑信息素浓度和启发式规则
        pheromone_values = pheromone[self.current_region]
        probabilities = [0.0] * num_regions

        for i in range(num_regions):
            if i != self.current_region:
                # 计算选择下一个区域的概率
                probabilities[i] = (pheromone_values[i] ** alpha) * (1 / demand[i])

        total_probability = sum(probabilities)
        # 归一化概率
        probabilities = [p / total_probability for p in probabilities]

        # 根据概率选择下一个区域
        next_region = random.choices(range(num_regions), probabilities)[0]
        return next_region

    def move_to_next_region(self, next_region):
        # 执行调度动作，更新路径
        self.tour.append(next_region)
        self.current_region = next_region

# 主循环
for iteration in range(num_iterations):
    ants = [Ant() for _ in range(num_ants)]

    for ant in ants:
        while ant.current_region != target_region:
            next_region = ant.select_next_region(target_region)
            ant.move_to_next_region(next_region)

    # 统计每个区域到目标区域的调度资源数量
    dispatch_count = [0] * num_regions
    for ant in ants:
        for region in ant.tour:
            dispatch_count[region] += 1

    # 输出每个区域到目标区域的调度资源数量
    print(f"第 {iteration + 1} 次迭代结果：")
    for i in range(num_regions):
        print(f"从区域 {i} 调度到目标区域的资源数量: {dispatch_count[i]}")

    # 更新信息素浓度矩阵
    for i in range(num_regions):
        for j in range(num_regions):
            if i != j:
                pheromone[i][j] *= (1 - evaporation_rate)

    for ant in ants:
        # 更新信息素浓度
        for i in range(len(ant.tour) - 1):
            start_region, end_region = ant.tour[i], ant.tour[i + 1]
            pheromone[start_region][end_region] += 1.0 / dispatch_count[start_region]

# 选择最优解决方案
best_ant = min(ants, key=lambda ant: sum([abs(demand[end] - max_capacity) for end in ant.tour]))

# 输出最优解决方案
print("最优调度方案：")
for region in best_ant.tour:
    print(f"从区域 {region} 调度到目标区域")
